<template>
    <div class="s-canvas">
        <canvas id="s-canvas" :width="contentWidth" :height="contentHeight"></canvas>
    </div>
</template>
<script setup lang="ts">
import { onMounted, watch } from 'vue'

const props = defineProps({
    identifyCode: {
        type: String,
        default: "1234",
    },
    fontSizeMin: {
        type: Number,
        default: 26,
    },
    fontSizeMax: {
        type: Number,
        default: 30,
    },
    backgroundColorMin: {
        type: Number,
        default: 180,
    },
    backgroundColorMax: {
        type: Number,
        default: 240,
    },
    colorMin: {
        type: Number,
        default: 50,
    },
    colorMax: {
        type: Number,
        default: 160,
    },
    lineColorMin: {
        type: Number,
        default: 40,
    },
    lineColorMax: {
        type: Number,
        default: 180,
    },
    dotColorMin: {
        type: Number,
        default: 0,
    },
    dotColorMax: {
        type: Number,
        default: 255,
    },
    contentWidth: {
        type: Number,
        default: 82,
    },
    contentHeight: {
        type: Number,
        default: 32,
    },
})
const randomNum = (min: number, max: number) => Math.floor(Math.random() * (max - min) + min)
const randomColor = (min: number, max: number) => {
    let r = randomNum(min, max)
    let g = randomNum(min, max)
    let b = randomNum(min, max)
    return "rgb(" + r + "," + g + "," + b + ")"
}
const drawText = (ctx: CanvasRenderingContext2D, txt: string, i: number) => {
    ctx.fillStyle = randomColor(props.colorMin, props.colorMax)
    ctx.font = randomNum(props.fontSizeMin, props.fontSizeMax) + "px SimHei"
    let x = (i + 1) * (props.contentWidth / (props.identifyCode.length + 3))
    let y = randomNum(props.fontSizeMax, props.contentHeight + 1)
    var deg = randomNum(-5, 5)
    // 修改坐标原点和旋转角度
    ctx.translate(x, y)
    ctx.rotate((deg * Math.PI) / 180)
    ctx.fillText(txt, 0, 0)
    // 恢复坐标原点和旋转角度
    ctx.rotate((-deg * Math.PI) / 180)
    ctx.translate(-x, -y)
}
const drawLine = (ctx: CanvasRenderingContext2D) => {
    // 绘制干扰线
    for (let i = 0; i < 6; i++) {
        ctx.strokeStyle = randomColor(props.lineColorMin, props.lineColorMax)
        ctx.beginPath()
        ctx.moveTo(randomNum(0, props.contentWidth), randomNum(0, props.contentHeight))
        ctx.lineTo(randomNum(0, props.contentWidth), randomNum(0, props.contentHeight))
        ctx.stroke()
    }
}
const drawDot = (ctx: CanvasRenderingContext2D) => {
    // 绘制干扰点
    for (let i = 0; i < 100; i++) {
        ctx.fillStyle = randomColor(0, 255)
        ctx.beginPath()
        ctx.arc(randomNum(0, props.contentWidth), randomNum(0, props.contentHeight), 1, 0, 2 * Math.PI)
        ctx.fill()
    }
}
const drawPic = () => {
    let canvas = document.getElementById("s-canvas") as HTMLCanvasElement
    let ctx = canvas.getContext("2d") as CanvasRenderingContext2D
    ctx.textBaseline = "bottom"
    // 绘制背景
    ctx.fillStyle = randomColor(props.backgroundColorMin, props.backgroundColorMax)
    ctx.fillRect(0, 0, props.contentWidth, props.contentHeight)
    // 绘制文字
    let arrcode = props.identifyCode.split(" ") as any
    for (let i = 0; i < arrcode.length; i++) {
        drawText(ctx, arrcode[i], i)
    }
    drawLine(ctx)
    drawDot(ctx)
}

watch(
    () => props.identifyCode,
    () => {
        drawPic()
    },
    {
        // immediate: true,
        deep: true,
    }
)

onMounted(() => {
    drawPic()
})
</script>
<style lang="scss" scoped>
.s-canvas {
    display: flex;
    align-items: center;
    cursor: pointer;

    #s-canvas {
        border-radius: 4px;
    }
}
</style>